package com.dh.jwt.auth;

import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Type;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpInputMessage;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.stereotype.Component;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.support.spring.FastJsonHttpMessageConverter4;
import com.dh.jwt.config.JwtProperties;
import com.dh.jwt.enums.BizExceptionEnum;
import com.dh.jwt.exception.BussinessException;
import com.dh.jwt.utils.HttpKit;
import com.dh.jwt.utils.JwtTokenUtil;
import com.dh.jwt.utils.MD5Util;

/**
 * 
* @ClassName: WithSignMessageConverter 
* @Description: 带签名的http信息转化器 
*               该转换器配置在FastjsonConfig中
* @author dinghao
* @date 2018年11月30日 下午4:21:08 
*
 */
@Component
public class WithSignMessageConverter extends FastJsonHttpMessageConverter4 {
	
	@Autowired
    JwtProperties jwtProperties;

    @Autowired
    JwtTokenUtil jwtTokenUtil;
    
    @Override
    public Object read(Type type, Class<?> contextClass, HttpInputMessage inputMessage)
    		throws IOException, HttpMessageNotReadableException {
    	InputStream in = inputMessage.getBody();
    	Object o = JSON.parseObject(in, super.getFastJsonConfig().getCharset(), BaseTransferEntity.class, super.getFastJsonConfig().getFeatures());
    	
    	//先转化成原始的对象
    	BaseTransferEntity baseTransferEntity = (BaseTransferEntity) o;
    	
    	//校验签名
    	String token = HttpKit.getRequest().getHeader(jwtProperties.getHeader()).substring(7);
    	String md5KeyFromToken = jwtTokenUtil.getMd5KeyFromToken(token);
    	
    	String json = JSON.toJSONString(baseTransferEntity.getObject());
    	String encrypt = MD5Util.encrypt(json + md5KeyFromToken);
    	
    	if (encrypt.equals(baseTransferEntity.getSign())) {
    		System.out.println("签名校验成功!");
    	} else {
    		System.out.println("签名校验失败,数据被改动过!");
    		throw new BussinessException(BizExceptionEnum.SIGN_ERROR);
    	}
    	
    	//校验签名后再转化成应该的对象
    	return JSON.parseObject(json, type);
    }
}
